<template>
  <el-container class="app-container">
    <el-aside width="50%" class="chart-container">
      <ECharts :options="chartOptions" />
    </el-aside>
    <el-main class="code-editor-container">
      <div id="monaco-container" class="code-editor"></div>
      <div class="button-group">
        <el-button type="primary" @click="runChartCode">运行</el-button>
        <el-select v-model="language" placeholder="选择语言" @change="updateEditorLanguage" style="margin-left: 10px; width: 150px;">
          <el-option label="JSON" value="json" />
          <el-option label="JavaScript" value="javascript" />
          <el-option label="TypeScript" value="typescript" />
        </el-select>
        <el-select v-model="theme" placeholder="选择主题" @change="updateTheme" style="margin-left: 10px; width: 150px;">
          <el-option label="默认" value="light" />
          <el-option label="深色" value="dark" />
        </el-select>
      </div>
    </el-main>
  </el-container>
</template>
<script lang="ts" setup>
import * as monaco from "monaco-editor";
import * as echarts from "echarts";
import { ref, onMounted, onBeforeUnmount } from "vue";
import ECharts from "../../../components/ECharts/ECharts.vue";

// 图表配置类型定义
interface ChartOptions {
  title: { text: string };
  xAxis: { type: string; data: string[] };
  yAxis: { type: string };
  series: { data: number[]; type: string }[];
}

// 初始图表配置
const chartOptions = ref<ChartOptions>({
  title: { text: "初始图表" },
  xAxis: { type: "category", data: ["Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"] },
  yAxis: { type: "value" },
  series: [{ data: [820, 932, 901, 934, 1290, 1330, 1320], type: "line" }],
});

// 响应式变量
const language = ref<"json" | "javascript" | "typescript">("json");
const theme = ref<"light" | "dark">("light");

// 编辑器实例
let editor: monaco.editor.IStandaloneCodeEditor | null = null;
let model: monaco.editor.ITextModel | null = null;

// 编辑器代码内容
const editorCode = ref<string>(
    JSON.stringify(chartOptions.value, null, 2) // 格式化 JSON 初始配置
);

// 创建 Monaco Editor 实例
onMounted(() => {
  model = monaco.editor.createModel(editorCode.value, "json");
  editor = monaco.editor.create(document.getElementById("monaco-container") as HTMLElement, {
    model,
    theme: "vs", // 默认浅色主题
    automaticLayout: true, // 自动布局
    scrollBeyondLastLine: false, // 禁用最后一行额外滚动
    minimap: { enabled: false }, // 禁用迷你地图
  });

  // 监听内容变化
  editor.onDidChangeModelContent(() => {
    editorCode.value = editor?.getValue() || "";
  });
});

// 销毁 Monaco Editor 实例
onBeforeUnmount(() => {
  if (editor) {
    editor.dispose();
  }
  if (model) {
    model.dispose();
  }
});

// 更新编辑器语言
const updateEditorLanguage = () => {
  if (editor && editor.getModel()) {
    const currentValue = editor.getValue();
    const newModel = monaco.editor.createModel(currentValue, language.value);
    editor.setModel(newModel);
    model = newModel; // 更新当前 model 引用
  } else {
    console.warn("Monaco Editor 未正确初始化或已销毁！");
  }
};

// 更新编辑器主题
const updateTheme = () => {
  if (editor) {
    monaco.editor.setTheme(theme.value === "dark" ? "vs-dark" : "vs");
  }
};

// 运行图表更新逻辑
const runChartCode = () => {
  try {
    if (language.value === "json") {
      // 处理 JSON 配置
      const updatedOptions: ChartOptions = JSON.parse(editor?.getValue() || "{}");
      chartOptions.value = updatedOptions;
    } else {
      // 处理 JavaScript/TypeScript 代码
      const code = editor?.getValue() || "";
      const wrappedCode = `
        let option;
        ${code}
        return option;
      `;
      const fn = new Function("chartOptions", "echarts", wrappedCode);
      const result = fn(chartOptions, echarts); // 执行用户代码
      if (result) {
        chartOptions.value = result; // 将返回的 `option` 更新到图表
      } else {
        console.warn("代码执行成功，但未生成有效的图表配置！");
      }
    }
  } catch (error) {
    console.error("运行代码出错:", error);
    alert(`代码运行出错：${error instanceof Error ? error.message : error}`);
  }
};


</script>
<style scoped>
.app-container {
  height: 100vh;
}

.chart-container {
  padding: 20px;
  background: #f0f2f5;
  border-right: 1px solid #eaeaea;
  display: flex;
  align-items: center;
  justify-content: center;
}

.code-editor-container {
  padding: 20px;
  background: #f9f9f9;
}

#monaco-container {
  width: 100%;
  height: 70vh;
  border: 1px solid #dcdfe6;
  border-radius: 4px;
}

.button-group {
  margin-top: 10px;
  display: flex;
  align-items: center;
}

.el-button {
  font-size: 14px;
}

.el-select {
  margin-left: 10px;
}
</style>
